import CardFunctions from "../Script/Common/CardFunctions";
import { Consts } from "../Script/Data/Consts";
import { GameData } from "../Script/Data/GameData";
import { 棋子Type } from "../Script/Data/GameEnum";
import CommonFunction from "../Script/utils/CommonFunction";
import FileMgr, { READ_FILE_TYPE } from "./FileMgr";
import Grid_BJQ from "./Grid_BJQ";

const { ccclass, property } = cc._decorator;

@ccclass
export default class EditorScene extends cc.Component {
    static Instance: EditorScene;

    @property(cc.Prefab)
    Prefab_Grid: cc.Prefab = null;
    @property(cc.Node)
    Root_grid: cc.Node = null;

    @property(cc.EditBox)
    EditBox_row: cc.EditBox = null;
    @property(cc.EditBox)
    EditBox_col: cc.EditBox = null;
    @property(cc.EditBox)
    EditBox_width: cc.EditBox = null;
    @property(cc.EditBox)
    EditBox_height: cc.EditBox = null;

    @property(cc.Button)
    Button_墙: cc.Button = null;
    @property(cc.Button)
    Button_平台: cc.Button = null;
    @property(cc.Button)
    Button_敌人: cc.Button = null;
    @property(cc.Button)
    Button_兵: cc.Button = null;
    @property(cc.Button)
    Button_马: cc.Button = null;
    @property(cc.Button)
    Button_象: cc.Button = null;
    @property(cc.Button)
    Button_车: cc.Button = null;
    @property(cc.Button)
    Button_王: cc.Button = null;
    @property(cc.Button)
    Button_后: cc.Button = null;

    @property(cc.Button)
    Button_清除选中: cc.Button = null;
    @property(cc.Button)
    Button_清除所有: cc.Button = null;

    @property(cc.Button)
    Button_保存文件: cc.Button = null;
    @property(cc.Button)
    Button_生成json: cc.Button = null;

    /** 场景编辑器mask节点 */
    @property(cc.Node)
    ndEditorMask: cc.Node = null;
    /** 选择框 */
    @property(cc.Node)
    ndSelectBox: cc.Node = null;

    width
    height

    onLoad() {
        EditorScene.Instance = this;
    }

    protected start(): void {
        this.AddListener();

        this.initCard();
    }

    async AddListener() {
        this.Button_墙.node.on("click", this.On_Button_墙, this);
        this.Button_平台.node.on("click", this.On_Button_平台, this);
        this.Button_敌人.node.on("click", this.On_Button_敌人, this);
        this.Button_兵.node.on("click", this.On_Button_兵, this);
        this.Button_马.node.on("click", this.On_Button_马, this);
        this.Button_象.node.on("click", this.On_Button_象, this);
        this.Button_车.node.on("click", this.On_Button_车, this);
        this.Button_王.node.on("click", this.On_Button_王, this);
        this.Button_后.node.on("click", this.On_Button_后, this);

        this.Button_清除选中.node.on("click", this.On_Button_清除选中, this);
        this.Button_清除所有.node.on("click", this.On_Button_清除所有, this);

        this.Button_保存文件.node.on("click", this.On_Button_读取文件, this);
        this.Button_生成json.node.on("click", this.On_Button_生成json, this);

        this.EditBox_row.node.on('editing-did-ended', this.on_EditBox_row, this);
        this.EditBox_col.node.on('editing-did-ended', this.on_EditBox_col, this);
        this.EditBox_width.node.on('editing-did-ended', this.on_EditBox_width, this);
        this.EditBox_height.node.on('editing-did-ended', this.on_EditBox_height, this);


        this.ndEditorMask.on(cc.Node.EventType.MOUSE_DOWN, this.onMouseDown, this);
        this.node.on(
            cc.Node.EventType.MOUSE_UP,
            (event: cc.Event.EventMouse) => {
                event.stopPropagation();
                if (cc.isValid(this.ndSelectBox)) {
                    this.ndSelectBox.active = false;
                }
                this.node.off(cc.Node.EventType.MOUSE_MOVE);

                this.AllGridSelect(false);
                for (let x = 0; x < GameData.col; x++) {
                    for (let y = 0; y < GameData.row; y++) {
                        const grid: Grid_BJQ = EditorScene.GetGrid(x, y);
                        if (grid) {
                            // console.log(grid);
                            let ischeck = CommonFunction.checkIntersectOrContain(grid.node, this.ndSelectBox);
                            if (ischeck) {
                                grid.Select(true);
                            }
                        }
                    }
                }
            }
        );
    }

    mouseMove4(event: cc.Event.EventMouse) {
        event.stopPropagation();
        const location = this.ndEditorMask.convertToNodeSpaceAR(
            event.getLocation()
        );
        const pst = this.ndSelectBox.position;
        this.ndSelectBox.anchorX = location.x > pst.x ? 0 : 1;
        this.ndSelectBox.anchorY = location.y > pst.y ? 0 : 1;
        this.ndSelectBox.position = pst;
        this.ndSelectBox.width = Math.abs(location.x - pst.x);
        this.ndSelectBox.height = Math.abs(location.y - pst.y);
    }

    private onMouseDown(event: cc.Event.EventMouse) {
        event.stopPropagation();

        // this.ndSelectBox.destroy();
        // this.ndSelectBox = cc.instantiate(this.pfSelectBox);
        this.ndSelectBox.width = 0;
        this.ndSelectBox.height = 0;
        this.ndSelectBox.active = true;

        // this.ndEditorMask.addChild(this.ndSelectBox);
        const location = event.getLocation();
        this.ndSelectBox.setPosition(
            this.ndEditorMask.convertToNodeSpaceAR(location)
        );

        this.node.on(
            cc.Node.EventType.MOUSE_MOVE,
            this.mouseMove4,
            this
        );
    }

    static GetGrid(x: number, y: number) {
        if (GameData.arrGrids[x] && GameData.arrGrids[x][y]) {
            return GameData.arrGrids[x][y];
        }
        return null;
    }

    static GetSelectGridList() {
        let arr = [];
        for (let x = 0; x < GameData.col; x++) {
            for (let y = 0; y < GameData.row; y++) {
                const grid: Grid_BJQ = EditorScene.GetGrid(x, y);
                if (grid && grid.isSelect) {
                    arr.push(grid);
                }
            }
        }
        return arr;
    }

    async On_Button_墙() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.墙);
            }
        }
    }
    async On_Button_平台() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.平台);
            }
        }
    }
    async On_Button_敌人() {
        console.log(`敌人`);
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.敌人);
            }
        }
    }
    async On_Button_兵() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.兵);
            }
        }
    }
    async On_Button_马() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.马);
            }
        }
    }
    async On_Button_象() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.象);
            }
        }
    }
    async On_Button_车() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.车);
            }
        }
    }
    async On_Button_王() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.王);
            }
        }
    }
    async On_Button_后() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(棋子Type.后);
            }
        }
    }

    async On_Button_清除选中() {
        let gridList = EditorScene.GetSelectGridList();
        if (gridList && gridList.length && gridList.length > 0) {
            for (let index = 0; index < gridList.length; index++) {
                const grid = gridList[index];
                grid.Set(null);
            }
        }
    }
    async On_Button_清除所有() {
        for (let x = 0; x < GameData.col; x++) {
            for (let y = 0; y < GameData.row; y++) {
                const grid: Grid_BJQ = EditorScene.GetGrid(x, y);
                if (grid) {
                    grid.Set(null);
                }
            }
        }
    }

    /** 导入关卡 */
    importLevel() {
        FileMgr.getInstance().openLocalFile("config.me", (file: File) => {
            if (file.type !== "application/json") {
                alert('导入失败，关卡数据必须为json');
                return;
            }
            FileMgr.getInstance().readLocalFile(file, READ_FILE_TYPE.TEXT, (res: string) => {
                GameData.CurrentLevelData = JSON.parse(String(res))
                console.log(`GameData.CurrentLevelData`, GameData.CurrentLevelData);

                GameData.row = GameData.CurrentLevelData.row;
                GameData.col = GameData.CurrentLevelData.col;

                this.initReadCard();

                // if (!(level && typeof level === "object" && level instanceof Array && level.every((layer) => typeof layer === 'string'))) {
                //     alert('导入失败，关卡数据格式不正确');
                //     return;
                // }
                // const name = file.name.slice(0, -5);
                // if (miscCtrl.getHasOwnLevel(name)) {
                //     const warnPanel = cc.instantiate(this.pfWarnPanel);
                //     warnPanel.getComponent(WarnPanel).init(WarnType.EXIST, () => {
                //         miscCtrl.setLevel(name, level);
                //         eventMgr.dispatchEvent(Consts.EventType.MERGE_LEVEL, name);
                //     }, `关卡《${name}》已存在，是否合并`);
                //     this.node.addChild(warnPanel);
                // }
                // else {
                //     miscCtrl.setLevel(name, level);
                //     this.createLevelTag(null, null, name);
                // }
            });
        });
    }

    async On_Button_读取文件() {
        this.importLevel();
    }
    async On_Button_生成json() {
        this.createJSON();
    }

    async on_EditBox_row() {
        this.initCard();
    }
    async on_EditBox_col() {
        this.initCard();
    }
    async on_EditBox_width() {
        this.initCard();
    }
    async on_EditBox_height() {
        this.initCard();
    }

    async initReadCard() {
        // GameData.row = parseInt(this.EditBox_row.string);
        // GameData.col = parseInt(this.EditBox_col.string);
        // this.width = parseInt(this.EditBox_width.string);
        // this.height = parseInt(this.EditBox_height.string);

        // console.log(GameData.row);
        // console.log(GameData.col);
        // console.log(this.width);
        // console.log(this.height);

        console.log(`读取文件加载`);


        this.Root_grid.destroyAllChildren();
        GameData.arrGrids = [];

        for (let x = 0; x < GameData.col; x++) {
            GameData.arrGrids[x] = [];
            for (let y = 0; y < GameData.row; y++) {
                const id = 0;
                // const scrGrid: Grid = CardFunctions.CreateGrid(id, x, y);
                console.log(id);

                const node: cc.Node = cc.instantiate(this.Prefab_Grid);
                const scrGrid: Grid_BJQ = node.getComponent(Grid_BJQ);
                scrGrid.init(id, x, y);
                // this.Root_grid.addChild(node);
                node.parent = this.Root_grid

                GameData.arrGrids[x][y] = scrGrid;
            }
        }

        console.log(GameData.CurrentLevelData);
        console.log(GameData.CurrentLevelData.map_data);

        for (let index = 0; index < GameData.CurrentLevelData.map_data.length; index++) {
            const data = GameData.CurrentLevelData.map_data[index];
            const grid: Grid_BJQ = EditorScene.GetGrid(data.x, data.y);
            grid.Set(data.棋子Type);
            // let block = CardFunctions.CreateBlock(data.x, data.y, id, 100);
        }
    }

    async initCard() {
        GameData.row = parseInt(this.EditBox_row.string);
        GameData.col = parseInt(this.EditBox_col.string);
        // GameData.size = parseInt(this.EditBox_width.string);

        // GameData.W = GameData.size * GameData.col;
        // GameData.H = GameData.size * GameData.row;

        console.log(GameData.row);
        console.log(GameData.col);
        console.log(this.width);
        console.log(this.height);

        this.Root_grid.destroyAllChildren();
        GameData.arrGrids = [];
        // this.node.width = GameData.W + 0;
        // this.node.height = GameData.H + 0;

        for (let x = 0; x < GameData.col; x++) {
            GameData.arrGrids[x] = [];
            for (let y = 0; y < GameData.row; y++) {
                const id = 0;
                // const scrGrid: Grid = CardFunctions.CreateGrid(id, x, y);
                console.log(id);

                const node: cc.Node = cc.instantiate(this.Prefab_Grid);
                const scrGrid: Grid_BJQ = node.getComponent(Grid_BJQ);
                scrGrid.init(id, x, y);
                // this.Root_grid.addChild(node);
                node.parent = this.Root_grid

                GameData.arrGrids[x][y] = scrGrid;
            }
        }
    }

    AllGridSelect(active: boolean) {
        for (let x = 0; x < GameData.col; x++) {
            for (let y = 0; y < GameData.row; y++) {
                const grid: Grid_BJQ = CardFunctions.Get_Grid(x, y);
                if (grid && grid.Image_point && grid.Image_point.node) {
                    grid.Select(active);
                }
            }
        }
    }

    /** 生成json文件 */
    createJSON() {
        let data: any = {
            row: GameData.row,
            col: GameData.col,
            map_data: [],
        };

        for (let x = 0; x < GameData.col; x++) {
            for (let y = 0; y < GameData.row; y++) {
                const grid: Grid_BJQ = CardFunctions.Get_Grid(x, y);
                if (grid) {
                    let item: any = {};
                    item.x = grid.col;
                    item.y = grid.row;
                    let isPush = false;

                    if (grid.墙类型) {
                        console.log(`grid.墙类型`, grid.墙类型)
                        isPush = true;
                        item.wall = true;
                    }
                    if (grid.平台类型) {
                        console.log(`grid.平台类型`, grid.平台类型)
                        isPush = true;
                        item.platform = true;
                    }
                    if (grid.棋子类型) {
                        console.log(`grid.棋子类型`, grid.棋子类型)
                        isPush = true;
                        item.棋子Type = grid.棋子类型;
                    }

                    if (isPush) {
                        data.map_data.push(item);
                    }
                }
            }
        }
        this.saveJSON(data, "1" + ".json");
    }

    saveJSON(data, filename) {
        if (!data) {
            alert('data is null');
            return;
        }
        if (!filename) {
            filename = 'json.json'
        }
        if (typeof data === 'object') {
            data = JSON.stringify(data, undefined, 4)
        }
        // 文件保存
        let blob = new Blob([data], { type: 'text/json' });
        let e = document.createEvent('MouseEvents');
        let a = document.createElement('a');
        a.download = filename;
        a.href = window.URL.createObjectURL(blob);
        a.dataset.downloadurl = ['text/json', a.download, a.href].join(':');
        e.initMouseEvent('click', true, false, window, 0, 0, 0, 0, 0, false, false, false, false, 0, null);
        a.dispatchEvent(e);
    }
}

/** 调试 */
window["EditorScene"] = EditorScene;